/*
 * ThreeAddress.h
 *
 *  Created on: 24/05/2010
 *      Author: rodolfo
 */

#ifndef THREEADDERESS_H_
#define THREEADDERESS_H_
#include"ThreeAddressInstruction.h"
#include "../analysis/parser/CompoundStatement.h"
#include "../analysis/parser/ExpressionStatement.h"
#include "../analysis/parser/BinaryExpression.h"
#include "../analysis/parser/UnaryExpression.h"
#include "../analysis/parser/CastExpression.h"
#include "../analysis/parser/Identifier.h"
#include "../analysis/parser/If.h"
#include "../analysis/parser/UnaryExpression.h"
#include "../analysis/parser/While.h"
#include "../analysis/parser/Do.h"
#include "../analysis/parser/For.h"
#include <string>
#include <sstream>
#include <iostream>
#include <vector>
#include <map>

class ThreeAddress {
public:
	ThreeAddress();
	virtual ~ThreeAddress();
	const std::vector<ThreeAddressInstruction>& getThreeAddressTable() const;
	void makeTable( Statement *stm ) ;
	void createLabels();
	int getLineCount() const{
		return lineCount;
	}
	void print();
	int getBasicBlocks( ) const {
		return basicBlocks;
	}
	
	std::map<int,int> getMapBlocks() const {
	    return mapBBlockPos;	
	}
	std::map<int,int> getMapLabels() const {
	    return mapLabelPos;
	}
	

private:
	std::vector<ThreeAddressInstruction> threeAddressTable;
	std::map<int,int> mapLabelPos;
	std::map<int,int> mapBBlockPos;
	int tempInstructionCount;
	int lineCount;
	int basicBlocks;
	std::string tempInstructionName;
	//methods
	const std::string& expressionAdd( Expression *expression );
	const std::string& binaryExpressionAdd( BinaryExpression *bExp );
	inline const std::string& binaryOp( BinaryExpression *bExp, std::string op );
	inline void assingmentOP(BinaryExpression *bExp, std::string op);
	const std::string& unaryExpressionAdd(UnaryExpression *unExp);
	inline const std::string& unaryOp(UnaryExpression *unExp, std::string op);
	const std::string& castExpressionAdd(CastExpression *castExp);
	const std::string& getTempInstructionName(){
		tempInstructionName = "Tmp"+convertToStr(tempInstructionCount);
		tempInstructionCount++;
		return tempInstructionName;
	}
	const std::string& changeOp( BinaryOperators op );
	const std::string& conditionResult( Expression *condition );
	std::string convertToStr( int value );
	int convertFromStr( std::string value );
	void fillMapBBPos();
};

#endif /* THREEADDERESS_H_ */
